﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using NHibernate.Cfg;
using FluentNHibernate.Cfg;
using FluentNHibernate.Cfg.Db;
using NH = NHibernate;
using cludg.Repository.NHibernate.Extensions;

namespace cludg.Repository.NHibernate.Config
{
	public static class ConfigProvider
	{
		private static IPersistenceConfigurer GetDbConfig(DbDriver dbDriver, string connectionString)
		{
			switch (dbDriver)
			{
				case DbDriver.SQLServer:
					return MsSqlConfiguration
						.MsSql2008
						.ConnectionString(connectionString)
						.Cache(x => x
							.UseQueryCache()
							.UseMinimalPuts()
							.ProviderClass<NH.Caches.SysCache2.SysCacheProvider>())
						.UseReflectionOptimizer();

				case DbDriver.SQLCompact:
					return MsSqlCeConfiguration
						.Standard
						.ConnectionString(connectionString)
						.Cache(x => x
							.UseQueryCache()
							.UseMinimalPuts()
							.ProviderClass<NH.Caches.SysCache2.SysCacheProvider>())
						.UseReflectionOptimizer();
			}
			return null;
		}

		public static Configuration GetConfig(
			DbDriver dbDriver,
			string connectionString,
			INHMappingExtensionRegistry mappingExtensionRegistry)
		{
			return Fluently.Configure()
				.Database(GetDbConfig(dbDriver, connectionString))
				.Mappings(x => x
							.ApplyExtensions(mappingExtensionRegistry.Get())
							.FluentMappings
								.Add<Content.StoryMap>()
								.Add<Content.StorySubjectMap>()
								.Add<Content.ImageSubjectMap>()
								.Add<Content.CommentMap>()
								.Add<Content.OfferMap>()
								.Add<Content.TagMap>()
								.Add<Environment.SettingMap>()
								.Add<Environment.HistoryEntryMap>()
								.Add<Security.UserMap>()
								.Add<Security.UserSecurityInfoMap>())
				.BuildConfiguration();
		}
	}

	internal static class MappingConfigurationHelper
	{
		public static MappingConfiguration ApplyExtensions(this MappingConfiguration cfg, IEnumerable<INHMappingExtension> extensions)
		{
			foreach (var extension in extensions)
			{
				extension.Execute(cfg);
			}
			return cfg;
		}
	}
}
